home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1996 May: Tool Chest / Developer CD Series May 1996 (Tool Chest) (Apple Computer) (1996).iso / Sample Code / Snippets / QuickDraw / FindFamilies / FindFamilies.c next >
Encoding:
C/C++ Source or Header  |  1994-02-24  |  9.7 KB  |  317 lines  |  [TEXT/MPS ]

  1. /******************************************************************************
  2. * FindFamilies
  3. *
  4. * (C)  Copyright Apple Computer, Inc. 1992
  5. * All rights reserved.
  6. *
  7. * by Matt Deatherage
  8. * Friday, October 2, 1992
  9. *
  10. * FindFamilies is an MPW tool that looks through 'FOND' resources.  You feed it
  11. * the name of a font family (like "Courier") and it examines the 'FOND' resource
  12. * for that family, printing the size and IDs of all resources that the 'FOND'
  13. * references.  It then walks through all your installed fonts and finds where
  14. * those are referenced.
  15. *
  16. * This is primarily useful for finding where style-linked fonts reside.  For
  17. * example, most fonts that ship with multiple styles include 'FOND' resources
  18. * describing the font and the main family.  MyFont Bold might have a 'FOND'
  19. * for a family named 'MyFont Bold' as well as a 'FOND' indicating it's the
  20. * "bold" entry for 'MyFont'.  
  21. *
  22. * Weird, huh?  As an example, I have the Monotype family Gill Sans installed
  23. * on my system.  The suitcase for "GillSans Bold" contains two entries -- one
  24. * indicating that the main font is the "plain" variety of "GillSans Bold" and
  25. * one indicating that Gill Sans Bold Italic is the "italic" variety of "GillSans
  26. * Bold".  GillSans Bold itself, though is the "bold" variety of "GillSans", so
  27. * there are multiple 'FOND's referencing the same fonts.  This reveals that
  28. * relationship.  Here's the sample output:
  29. *
  30. *    findfamilies "GillSans Bold"
  31. *    Source FOND GillSans Bold contains 1 entries:
  32. *
  33. *   Entry 0:  Size  12, ID 30684
  34. *   Entry 1:  Size  12, ID 30671
  35. *
  36. *    Now checking family: GillSans
  37. *       GillSans includes size 12 and ID 30684.
  38. *       GillSans includes size 12 and ID 30671.
  39. *    Now checking family: GillSans Bold
  40. *       GillSans Bold includes size 12 and ID 30684.
  41. *       GillSans Bold includes size 12 and ID 30671.
  42. *    Now checking family: GillSans Condensed
  43. *    Now checking family: GillSans BoldCondensed
  44. *    Now checking family: GillSans Italic
  45. *       GillSans Italic includes size 12 and ID 30671.
  46. *    Now checking family: GillSans BoldItalic
  47. *       GillSans BoldItalic includes size 12 and ID 30671.
  48. *
  49. * Files:
  50. *
  51. *    FindFamilies.c
  52. *    FindFamilies.make
  53. *
  54. * Version    1.0        MD
  55. *
  56. * Done in 1992, but first released in 1994.
  57. *
  58. *
  59. ******************************************************************************/
  60.  
  61. #include <stdio.h>
  62. #include <stdlib.h>
  63. #include <string.h>
  64. #include <strings.h>
  65. #include <fonts.h>
  66. #include <resources.h>
  67. #include <OSUtils.h>
  68. #include <GestaltEqu.h>
  69. #include <Folders.h>
  70. #include <memory.h>
  71.  
  72. /******************************************************************************
  73. *
  74. * Some things for the Fonts folder in 7.1 that aren't in the header files
  75. * on the GM disk.  These things are defined in ETO #13 headers, so if you have
  76. * those or later, you don't need to uncomment the GetNextFOND declaration.
  77. *
  78. ******************************************************************************/
  79.  
  80. #define kFontFolderType 'font'
  81. // pascal Handle GetNextFOND(Handle fondHandle) = {0x700A, 0xA822};
  82.  
  83. /*  These are #defined here because if they're not, some of the expressions below
  84.     get really ugly...   */
  85.     
  86. #define destEntry (*((AsscEntry **)destAsscTableHandle))
  87. #define srcEntry (*((AsscEntry **)srcAsscTableHandle))
  88.     
  89.     
  90.  
  91. /******************************************************************************
  92. *
  93. * Typedefs, etc.
  94. *
  95. ******************************************************************************/
  96.  
  97.  
  98. /******************************************************************************
  99. *
  100. * Prototypes
  101. *
  102. ******************************************************************************/
  103.  
  104.  
  105.  
  106. Handle FindFamilyFOND (char *familyName);
  107. Boolean IsFontsFolder (void);
  108. short BuildAsscTableHandle (Handle fondHandle, Handle *theNewHandle);
  109. void CheckTables(short numSrcEntries, short numDestEntries, Handle srcAsscTableHandle,
  110.                  Handle destAsscTableHandle, Str255 theName);
  111.                  
  112.  
  113.  
  114. /******************************************************************************
  115. *
  116. *     IsFontsFolder returns TRUE if the Fonts folder (and therefore, GetNextFOND
  117. *    is present, and FALSE if it's not.
  118. *
  119. ******************************************************************************/
  120.  
  121. Boolean IsFontsFolder (void)
  122. {
  123.  
  124.     Boolean foundIt;
  125.     OSErr myError;
  126.     long feature;
  127.     
  128.     short foundRefNum;
  129.     long foundDirID;
  130.     
  131.     #define Gestalttest        0xA1AD
  132.     #define NoTrap            0xA89F
  133.  
  134.     foundIt = false;        /* just in case */
  135.     
  136.     if ((NGetTrapAddress(Gestalttest,OSTrap) != NGetTrapAddress(NoTrap,ToolTrap))) {
  137.         myError = Gestalt(gestaltFindFolderAttr, &feature);
  138.         if (!myError) {
  139.             if (feature & gestaltFindFolderPresent) {
  140.                 myError = FindFolder(kOnSystemDisk,kFontFolderType,kDontCreateFolder,
  141.                                         &foundRefNum, &foundDirID);
  142.                                      
  143.                 if (!myError) 
  144.                     foundIt = true;        /* All we care about is finding it */
  145.             }
  146.         }                  
  147.     }
  148.     
  149.     return foundIt;
  150.  
  151. }
  152.  
  153.  
  154. /************************************************************************
  155. *
  156. *    FindFamilyFOND takes the given font family name and finds the FOND (or, in
  157. *    System 7.1, the first FOND) for that family name.
  158. *    
  159. *************************************************************************/
  160.  
  161. Handle FindFamilyFOND (char *familyName)
  162. {
  163.     Str255 nameString;
  164.     Handle theHandle;
  165.     OSErr myError;
  166.     
  167.     strcpy(nameString, familyName );        /* copy to not mess with original */
  168.     theHandle = GetNamedResource('FOND',c2pstr(nameString));
  169.     if ((((myError = ResError()) != noErr)) || (theHandle == NULL)) {
  170.         printf("Error getting %s FOND resource -- %d\n",familyName,myError);
  171.     }
  172.     return theHandle;
  173.     
  174. }
  175.  
  176. /******************************************************************************
  177. *
  178. * CheckTables takes two handles to font association tables and a count of the
  179. * number of entries in each and prints a warning if any of them match.  It
  180. * also takes a Str255 with the name of the destination FOND for printing.
  181. *
  182. ******************************************************************************/
  183.  
  184. void CheckTables(short numSrcEntries, short numDestEntries, Handle srcAsscTableHandle,
  185.                  Handle destAsscTableHandle, Str255 theName)
  186. {
  187.  
  188.     short countSrc, countDest;
  189.     int ignore;
  190.     
  191.     for (countSrc = 0; countSrc <= numSrcEntries; countSrc++) {
  192.         for (countDest = 0; countDest <= numDestEntries; countDest++) {
  193.             if ((srcEntry[countSrc].fontSize == destEntry[countDest].fontSize)  &&
  194.                 (srcEntry[countSrc].fontID == destEntry[countDest].fontID))
  195.                 ignore = printf("   %s includes size %d and ID %d.\n",theName,
  196.                                 srcEntry[countSrc].fontSize, srcEntry[countSrc].fontID);
  197.         }
  198.     }
  199. }
  200.  
  201. /******************************************************************************
  202. *
  203. * PrintTable prints all the entries in a table, enclosed in a handle.
  204. *
  205. ******************************************************************************/
  206.  
  207. void PrintTable(short count, Handle srcAsscTableHandle, Str255 theName)
  208. {
  209.  
  210.     short tempCount;
  211.     
  212.     printf("Source FOND %s contains %d entries:\n\n",theName,count+1);
  213.     
  214.     for (tempCount = 0; tempCount <= count; tempCount++) {
  215.         printf("   Entry %d:  Size %3d, ID %5d\n",tempCount,srcEntry[tempCount].fontSize,srcEntry[tempCount].fontID);
  216.     }
  217. }
  218.  
  219.  
  220.         
  221. /******************************************************************************
  222. *
  223. * BuildAsscTableHandle returns a new handle that contains a copy of a FOND's
  224. * association table.  The FOND handle is passed as input, as is a pointer to
  225. * the place to return the handle.  The result is a short indicating how many
  226. * entries are in the table.
  227. *
  228. ******************************************************************************/
  229.  
  230. short BuildAsscTableHandle (Handle fondHandle, Handle *theNewHandle)
  231. {
  232.  
  233.     OSErr myErr;
  234.     short theCount;
  235.     Ptr tempPtr;
  236.     
  237.     tempPtr = *fondHandle;
  238.     tempPtr += sizeof(FamRec);
  239.     theCount = (* ((short *)tempPtr));
  240.     
  241.     tempPtr += sizeof(short);                /* move past the count */
  242.     
  243.     myErr = PtrToHand(tempPtr, theNewHandle, (sizeof(AsscEntry) * (theCount+1)));
  244.     if (myErr) {
  245.         printf("### Nasty memory error -- %d",MemError());
  246.         exit(1);
  247.     }
  248.     
  249.     return theCount;
  250. }
  251.  
  252. int main(int argc, char * argv[])
  253. {
  254.     Boolean gHasFontsFolder = false;
  255.     short numFONDs, numSrcEntries, numDestEntries;
  256.     short tempID, ignore;
  257.     OSType tempType;
  258.     Str255 tempName;
  259.     short countFONDs;
  260.     Handle srcFONDHandle, srcAsscTableHandle, destFONDHandle, destAsscTableHandle;
  261.  
  262.     if (argc != 2 ) {
  263.         printf("### Usage:  FindFamilies fontfamilyname\n");
  264.         exit(1);
  265.     }
  266.     gHasFontsFolder = IsFontsFolder();    
  267.  
  268.     numFONDs = CountResources('FOND');
  269.     srcFONDHandle = FindFamilyFOND(argv[1]);
  270.     if (srcFONDHandle != NULL) {
  271.         numSrcEntries = BuildAsscTableHandle(srcFONDHandle, &srcAsscTableHandle);
  272.         GetResInfo(srcFONDHandle, &tempID, &tempType, &tempName);
  273.         p2cstr(tempName);
  274.         PrintTable(numSrcEntries, srcAsscTableHandle, tempName);   
  275.         
  276.         for (countFONDs = 1;countFONDs <= numFONDs;countFONDs++) {
  277.             destFONDHandle = GetIndResource('FOND',countFONDs);
  278.     
  279.             if (destFONDHandle != NULL) {
  280.                 GetResInfo(destFONDHandle, &tempID, &tempType, &tempName);
  281.                 p2cstr(tempName);
  282.                 ignore = printf("Now checking family: %s\n",tempName);   
  283.         
  284.                 numDestEntries = BuildAsscTableHandle(destFONDHandle, &destAsscTableHandle);
  285. /*                PrintTable(numDestEntries, destAsscTableHandle, tempName);   */
  286.                 
  287.                 CheckTables(numSrcEntries, numDestEntries, srcAsscTableHandle, destAsscTableHandle,
  288.                             tempName)    ;    
  289.                 DisposeHandle(destAsscTableHandle);
  290.             
  291.                 if (gHasFontsFolder) {
  292.                     destFONDHandle = GetNextFOND(destFONDHandle);
  293.                     while (destFONDHandle != NULL) {
  294.                         numDestEntries = BuildAsscTableHandle(destFONDHandle, &destAsscTableHandle);
  295.                         CheckTables(numSrcEntries, numDestEntries, srcAsscTableHandle, destAsscTableHandle,
  296.                                     tempName);    
  297.                         DisposeHandle(destAsscTableHandle);
  298.                     }
  299.                 }
  300.                 
  301.                 ReleaseResource(destFONDHandle);
  302.             } else {
  303.                 printf("Error getting  FOND resource #%d\n",countFONDs);
  304.             }
  305.             
  306.         }
  307.     } else 
  308.         printf("Source FOND could not be loaded.\n");
  309.     
  310.     ReleaseResource(srcFONDHandle);
  311.     ignore = printf("Checking complete.\n");
  312.     return 0;
  313.     
  314.  
  315. }
  316.  
  317.